#define NOMINMAX
#include "CreditDebtRankingList.h"
#include "../StringResource.h"
#include "../data/CreditDebtRankingData.h"
#include "../FIModule.h"
#include <core/StyleMgr.h>
#include <core/ImageMgr.h>
#include <widgets/table/STable.h>
#include <widgets/table/STableColumnSet.h>
#include <widgets/SCheckComboBox.h>
#include <QVBoxLayout>
#include <QMouseEvent>
#include <QTableView>
#include <QHeaderView>
#include <uam/ServerTimeMgr.h>
#include <bondlib/BondContainer.h>
#include <bondlib/BondAuctionInfo.h>
#include <qbtools/tools.h>
#include <bondlib/SSVContainer.h>
#include <qbprotocol/include/SSQBModel.h>
#include <guiframe/IModule.h>
#include <include/CmdDefines.h>
#include <qbbond/BondColDelegate.h>
#include <bondlib/BondCalendar.h>

#define ALIGN_LEFT   (Qt::Alignment)(Qt::AlignVCenter|Qt::AlignLeft)
#define ALIGN_RIGHT  (Qt::Alignment)(Qt::AlignVCenter|Qt::AlignRight)

CreditDebtRankingList::CreditDebtRankingList(QWidget* p, CreditDebtRankingData* data)
	: QWidget(p),
	  m_table(nullptr),
	  m_model(nullptr),
	  m_tableSet(nullptr),
	  m_data(data)
{
	m_table = new SVirtualTable(this);
	m_model = new DefaultTableModel(this);
	m_model->setTable(m_table);
	m_table->setHeaderSortable(true);
	m_table->table()->setModel(m_model);
	m_table->table()->horizontalHeader()->setSectionResizeMode(QHeaderView::Interactive);
	m_table->table()->horizontalHeader()->setSectionsMovable(true);
	m_table->table()->horizontalHeader()->show();
	connect(m_table, &SVirtualTable::headerSort, this, &CreditDebtRankingList::onHeaderSort);
	connect(m_table->table(), &QTableView::doubleClicked, this, &CreditDebtRankingList::onTableRowDblClicked);

	QVBoxLayout* mainLayout = new QVBoxLayout(this);
	mainLayout->setContentsMargins(0,0,0,0);
	mainLayout->addWidget(m_table);
	setLayout(mainLayout);
}

void CreditDebtRankingList::onTableRowDblClicked(const QModelIndex& index)
{
	QString bondIdx = index.data(DataIdRole).toString();
	if (!bondIdx.isEmpty()){
		int bondIndex = bondIdx.toInt();
		if (CBondContainer::instance().IsValidIndex(bondIndex))return;
		const CBondInfo& bond = CBondContainer::instance().ElementAtR(bondIndex);
		CmdInfo ci(CMD_BondDetail, 0, bond.GetCombBondKey(), nullptr);
		FIModule::instance().execCommand(ci);
	}
}

void CreditDebtRankingList::setData(CreditDebtRankingData* data)
{
	m_data = data;
}

void CreditDebtRankingList::onReloadData()
{
	loadData();
	updateTable(true);
}

void CreditDebtRankingList::loadData()
{
	m_lstPDeal.clear();
	if (m_data) {
		m_data->getTopDealData(m_lstPDeal, m_datainfo.type, m_datainfo.count, m_datainfo.needcount);
	}

	if (m_sortinfo.GetSize() > 0) {
		CSortInfo sortinfo;
		for (size_t i=0; i<m_cols.size(); i++) {
			sortKey key = getSortKey(i);
			if (key == emKey_Unkown) {
				continue;
			}
			if (!m_sortinfo.HasSortKey(key)) {
				continue;
			}
			if (!m_sortinfo.GetSortInfo(key, sortinfo)) {
				continue;
			}
			std::sort(m_lstPDeal.begin(), m_lstPDeal.end(), NewBondPanDealSorter(sortinfo.m_nSortKey, sortinfo.m_bDesc));
			break;
		}
	}
}

void CreditDebtRankingList::onHeaderSort(int col)
{
	m_sortinfo.AddOrUpdate(false, getSortKey(col));
	updateTableHeader();
	if (m_sortinfo.GetSize() > 0) {
		onReloadData();
	}
}

void CreditDebtRankingList::updateTableHeader()
{
	DefaultTableModel* dataModel = dynamic_cast<DefaultTableModel*>(m_table->table()->model());
	if (!dataModel) {
		return;
	}

	CSortInfo sortinfo;
	for (size_t i=0; i<m_cols.size(); i++) {
		ColumnInfo ci = m_tableSet->colInfoByIndex(i);
		sortKey key = getSortKey(i);
		if (m_sortinfo.GetSortInfo(key, sortinfo)) {
			QString prefix = sortinfo.m_bDesc ? "↓ " : "↑ ";
			dataModel->setHeaderData(i, Qt::Horizontal, prefix+ci.name);
		}
		else {
			dataModel->setHeaderData(i, Qt::Horizontal, ci.name);
		}
	}
}

void CreditDebtRankingList::updateFlash() {
	auto fnFindBond = [&](const char* code)->bool {
		for (size_t i = 0; i < m_lstPDeal.size(); i++) {
			if (strcmp(m_lstPDeal[i].m_bondCode, code) == 0) {
				return true;
			}
		}
		return false;
	};

	const std::list<std::string>& lstFlash = m_data->getFlash();
	if (lstFlash.size() > 0) {
		for (auto& it : lstFlash){
			if (fnFindBond(it.c_str())) {
				FlashInfo fi;
				fi.entireRow = true;
				fi.id = QString::fromLocal8Bit(it.c_str());
				m_table->addFlashInfo(fi, false);
			}
		}
		m_table->startFlash();
	}
}

//////////////////////////////////////////////////////////////////////////
CreditDebtRankingActiveList::CreditDebtRankingActiveList(QWidget* p, CreditDebtRankingData* data)
	: CreditDebtRankingList(p, data)
{
	m_sortinfo.InitData(getSortKey(fuCol_COUNT), true);
	m_datainfo.type = CreditDebtRankingData::type_Active;
	m_datainfo.count = 20;
	m_datainfo.needcount = false;
	initTable();
	RemainDateDelegate* rankActiveDelegate = new RemainDateDelegate(m_table, m_tableSet, TopOrBottomCursor);
	m_table->table()->setItemDelegateForColumn(fuCol_REMAIN, rankActiveDelegate);
	updateTableHeader();
}

void CreditDebtRankingActiveList::initTable()
{
	m_tableSet = new STableColumnSet(m_table, "CreditDebtRankingActiveList", this);
	m_tableSet->setSaveCfg(true);

	BEGIN_COLUMN;
	ADD_COLUMN(fuCol_REMAIN, m_tableSet, NewStringTable::strFixedIncomeActiveDeal(fuCol_REMAIN), 0, 50, 50, 0.14, false, ALIGN_LEFT, kAuto, "");
	m_cols.push_back(fuCol_REMAIN);
	ADD_COLUMN(fuCol_SHORT, m_tableSet, NewStringTable::strFixedIncomeActiveDeal(fuCol_SHORT), 0, 50, 50, 0.14, false, ALIGN_LEFT, kAuto, "");
	m_cols.push_back(fuCol_SHORT);
	ADD_COLUMN(fuCol_COUNT, m_tableSet, NewStringTable::strFixedIncomeActiveDeal(fuCol_COUNT), 0, 50, 50, 0.14, false, ALIGN_RIGHT, kAuto, "");
	m_cols.push_back(fuCol_COUNT);
	ADD_COLUMN(fuCol_ADV, m_tableSet, NewStringTable::strFixedIncomeActiveDeal(fuCol_ADV), 0, 50, 50, 0.14, false, ALIGN_RIGHT, kAuto, "");
	m_cols.push_back(fuCol_ADV);
	ADD_COLUMN(fuCol_YES, m_tableSet, NewStringTable::strFixedIncomeActiveDeal(fuCol_YES), 0, 50, 50, 0.14, false, ALIGN_RIGHT, kAuto, "");
	m_cols.push_back(fuCol_YES);
	ADD_COLUMN(fuCol_HIGH, m_tableSet, NewStringTable::strFixedIncomeActiveDeal(fuCol_HIGH), 0, 50, 50, 0.14, false, ALIGN_RIGHT, kAuto, "");
	m_cols.push_back(fuCol_HIGH);
	ADD_COLUMN(fuCol_LOW, m_tableSet, NewStringTable::strFixedIncomeActiveDeal(fuCol_LOW), 0, 50, 50, 0.12, false, ALIGN_RIGHT, kAuto, "");
	m_cols.push_back(fuCol_LOW);
	m_tableSet->apply();
	//m_tableSet->setFrozenCols(2);

	m_tableSet->setMenuCfg(kDft);
	connect(m_table, &SVirtualTable::viewPosChanged, [=](int){ updateTable(false); });
}

sortKey CreditDebtRankingActiveList::getSortKey(int col) {
	switch (col) {
	case fuCol_REMAIN: return emKey_Remain;
	case fuCol_SHORT: return emKey_Short;
	case fuCol_COUNT: return emKey_Count;
	case fuCol_ADV: return emKey_Adv;
	case fuCol_YES: return emKey_Yes;
	case fuCol_HIGH: return emKey_High;
	case fuCol_LOW: return emKey_Low;
	default: return emKey_Unkown;
	}
}

void CreditDebtRankingActiveList::updateTable(bool reset)
{
	QFont f = font();
	f.setPixelSize(13);
	f.setBold(true);

	unsigned int today = ServerTimeMgr::instance().today();
	QString strText;
	CBondContainer& bc = CBondContainer::instance();

	m_table->clearTable();

	int realCount = m_lstPDeal.size();
	int pageCount = m_table->pageCount();
	pageCount = std::min(pageCount, realCount);
	int pos = reset ? 0 : m_table->sliderPos();
	m_table->setRealDataCount(realCount);

	int colCount = m_model->columnCount();
	for (int row=0; row<pageCount; ++row)
	{
		if (pos+row<0 || pos+row>=(int)m_lstPDeal.size()) {
			break;
		}

		const CNewBondPanDeal& panDeal = m_lstPDeal[pos + row];
		int bondIndex = CBondContainer::instance().GetBondIndex(panDeal.m_bondkey, panDeal.m_listedmarket);
		if (!CBondContainer::instance().IsValidIndex(bondIndex)) return;
		const CBondInfo& bi = bc.ElementAtR(bondIndex);

		for (int col=0; col<colCount; ++col)
		{
			if (!m_tableSet->isColVisible(col))
				continue;

			QStandardItem* item = m_model->item(row, col);
			if (item == nullptr) {
				item = new QStandardItem();
			}
			item->clearData();
			item->setData(StyleMgr::instance().color("Highlight"), Qt::ForegroundRole);
			item->setData((int)(Qt::AlignLeft | Qt::AlignVCenter), Qt::TextAlignmentRole);
			item->setData(StyleMgr::instance().color("BasicPlate"), Qt::BackgroundRole);
			item->setData(f, Qt::FontRole);
			QString idStr = QString::fromLocal8Bit(bi.GetBondCode());
			item->setData(idStr, DataIdRole);

			switch (col) {
			case fuCol_REMAIN: {//期限
				time_t tServerTime = CSSVContainer::GetServerTime();
				strText = QString::asprintf("%s", bi.GetRemainPeriod(tServerTime));
				item->setData(strText, Qt::DisplayRole);

				int holidayType = emHolidayNull;
				QString strHolidayDays;
				bool isCIB = true;
				int nDayCIB = 0, nDaySSE = 0;
				if (CBondCalendar::instance().IsHoliday_CHY(bi, isCIB, nDayCIB, nDaySSE)){
					if (isCIB){
						if (nDayCIB == nDaySSE){
							strHolidayDays = QString::number(nDayCIB);
						}else{
							strHolidayDays = QString("%1/%2").arg(nDayCIB).arg(nDaySSE);
						}
						holidayType = emHolidayCib;
					}else{
						holidayType = emHolidaySSE;
						strHolidayDays = QString::number(nDaySSE);
					}
					item->setData(holidayType, HolidayTypeRole);			//存休息类型
					item->setData(strHolidayDays, HolidayNumberRole);	//存休息时间
					int maturityDay = atoi(bi.GetMaturityDate());
					item->setData(maturityDay, MaturityDayRole);
				}
				break;
			}
			case fuCol_SHORT: {//债券简称			
				strText = QString::fromLocal8Bit(bi.GetBondShortName());
				item->setData(strText, Qt::DisplayRole);
				break;
			}
			case fuCol_COUNT: {//成交笔数
				strText = QString::asprintf("%d", panDeal.m_nCount);
				item->setData((int)(Qt::AlignRight | Qt::AlignVCenter), Qt::TextAlignmentRole);
				item->setData(strText, Qt::DisplayRole);
				break;
			}
			case fuCol_ADV: {//平均成交
				if (panDeal.m_dbAdv > 0.00001) {
					strText = QString::asprintf("%.3f", panDeal.m_dbAdv);
					strText = SSTools::PriceRemoveZero(strText, 3);
				}
				else {
					strText = "--";
				}
				item->setData((int)(Qt::AlignRight | Qt::AlignVCenter), Qt::TextAlignmentRole);
				item->setData(strText, Qt::DisplayRole);
				break;
			}
			case fuCol_YES: {//昨日成交
				if (atof(panDeal.m_preAdv) > 0.00001) {
					strText = QString::asprintf("%s", panDeal.m_preAdv);
					strText = SSTools::PriceRemoveZero(strText, 3);
				}
				else {
					strText = "--";
				}
				item->setData((int)(Qt::AlignRight | Qt::AlignVCenter), Qt::TextAlignmentRole);
				item->setData(strText, Qt::DisplayRole);
				break;
			}
			case fuCol_HIGH: {//最高
				if (panDeal.m_dbLow > 0.00001) {
					if (panDeal.IsCleanPrice() || panDeal.IsFullPrice()) strText = QString::asprintf("%.3f", panDeal.m_dbHigh);
					else strText = QString::asprintf("%.3f", panDeal.m_dbLow);
					strText = SSTools::PriceRemoveZero(strText, 3);
				}
				else {
					strText = "--";
				}
				item->setData((int)(Qt::AlignRight | Qt::AlignVCenter), Qt::TextAlignmentRole);
				item->setData(strText, Qt::DisplayRole);
				break;
			}
			case fuCol_LOW: {//最低
				if (panDeal.m_dbHigh > 0.00001) {
					if (panDeal.IsCleanPrice() || panDeal.IsFullPrice()) strText = QString::asprintf("%.3f", panDeal.m_dbLow);
					else strText = QString::asprintf("%.3f", panDeal.m_dbHigh);
					strText = SSTools::PriceRemoveZero(strText, 3);
				}
				else {
					strText = "--";
				}
				item->setData((int)(Qt::AlignRight | Qt::AlignVCenter), Qt::TextAlignmentRole);
				item->setData(strText, Qt::DisplayRole);
				break;
			}
			default:
				break;
			}
			m_model->setItem(row, col, item);
		}
	}

	updateFlash();
}

//////////////////////////////////////////////////////////////////////////
CreditDebtRankingUpdownList::CreditDebtRankingUpdownList(QWidget* p, CreditDebtRankingData* data, emType type)
	: CreditDebtRankingList(p, data),
	  m_type(type)
{
	m_sortinfo.InitData(getSortKey(fuCol_UP), true);
	m_datainfo.type = (m_type==emTypeDown ? CreditDebtRankingData::type_DeviateDown : CreditDebtRankingData::type_DeviateUp);
	m_datainfo.count = 50;
	m_datainfo.needcount = true;
	initTable();
	updateTableHeader();
}

void CreditDebtRankingUpdownList::initTable()
{
	m_tableSet = new STableColumnSet(m_table, m_type==emTypeUp?"CreditDebtRankingUpList":"CreditDebtRankingDownList", this);
	m_tableSet->setSaveCfg(true);

	BEGIN_COLUMN;
	ADD_COLUMN(fuCol_SHORT, m_tableSet, NewStringTable::strFixedIncomeTop50AndBottom50(fuCol_SHORT), 0, 50, 50, 0.33, false, ALIGN_LEFT, kAuto, "");
	m_cols.push_back(fuCol_SHORT);
	ADD_COLUMN(fuCol_UP, m_tableSet, NewStringTable::strFixedIncomeTop50AndBottom50(fuCol_UP), 0, 50, 50, 0.33, false, ALIGN_RIGHT, kAuto, "");
	m_cols.push_back(fuCol_UP);
	ADD_COLUMN(fuCol_UPBP, m_tableSet, NewStringTable::strFixedIncomeTop50AndBottom50(fuCol_UPBP), 0, 50, 50, 0.34, false, ALIGN_RIGHT, kAuto, "");
	m_cols.push_back(fuCol_UPBP);

	m_tableSet->setMenuCfg(kDft);
	m_tableSet->apply();
	connect(m_table, &SVirtualTable::viewPosChanged, [=](int){updateTable(false);});
}

void CreditDebtRankingUpdownList::updateTable(bool reset)
{
	QFont f = font();
	f.setPixelSize(13);
	f.setBold(true);

	unsigned int today = ServerTimeMgr::instance().today();
	QString strText;
	CBondContainer& bc = CBondContainer::instance();

	m_table->clearTable();

	int realCount = m_lstPDeal.size();
	int pageCount = m_table->pageCount();
	pageCount = std::min(pageCount, realCount);
	int pos = reset ? 0 : m_table->sliderPos();
	m_table->setRealDataCount(realCount);

	int colCount = m_model->columnCount();
	for (int row = 0; row < pageCount; ++row)
	{
		if (pos + row < 0 || pos + row >= (int)m_lstPDeal.size()) {
			break;
		}

		const CNewBondPanDeal& panDeal = m_lstPDeal[pos + row];
		int bondIndex = CBondContainer::instance().GetBondIndex(panDeal.m_bondkey, panDeal.m_listedmarket);
		if (!CBondContainer::instance().IsValidIndex(bondIndex)) return;
		const CBondInfo& bi = bc.ElementAtR(bondIndex);

		for (int col = 0; col < colCount; ++col)
		{
			if (!m_tableSet->isColVisible(col))
				continue;

			QStandardItem* item = m_model->item(row, col);
			if (item == nullptr) {
				item = new QStandardItem();
			}
			item->clearData();
			item->setData(StyleMgr::instance().color("Highlight"), Qt::ForegroundRole);
			item->setData((int)(Qt::AlignLeft | Qt::AlignVCenter), Qt::TextAlignmentRole);
			item->setData(StyleMgr::instance().color("BasicPlate"), Qt::BackgroundRole);
			item->setData(f, Qt::FontRole);
			QString idStr = QString::fromLocal8Bit(bi.GetBondCode());
			item->setData(idStr, DataIdRole);

			switch (col) {
			case fuCol_SHORT: {//债券简称			
				strText = QString::fromLocal8Bit(bi.GetBondShortName());
				item->setData(strText, Qt::DisplayRole);
				break;
			}
			case fuCol_UP: { //净价偏离
				double tmpVal = panDeal.m_cdcGapPercent;
				if (m_type == emTypeDown) strText = QString::asprintf("%.4f", -tmpVal);
				else strText = QString::asprintf("%.4f", tmpVal);
				QColor color = StyleMgr::instance().color("Highlight");
				setDoubleColor(tmpVal, color, strText, true);
				item->setData(color, Qt::ForegroundRole);
				item->setData((int)(Qt::AlignRight | Qt::AlignVCenter), Qt::TextAlignmentRole);
				item->setData(strText, Qt::DisplayRole);
				break;
			}
			case fuCol_UPBP: {//偏离Bp
				double tmpVal = panDeal.m_cdcGapBP;
				if (m_type == emTypeDown) strText = QString::asprintf("%.4f", -tmpVal);
				else strText = QString::asprintf("%.4f", tmpVal);
				QColor color = StyleMgr::instance().color("Highlight");
				setDoubleColor(tmpVal, color, strText, false, true);
				item->setData(color, Qt::ForegroundRole);
				item->setData((int)(Qt::AlignRight | Qt::AlignVCenter), Qt::TextAlignmentRole);
				item->setData(strText, Qt::DisplayRole);
				break;
			}
			default:
				break;
			}
			m_model->setItem(row, col, item);
		}
	}

	updateFlash();
}

sortKey CreditDebtRankingUpdownList::getSortKey(int col)
{
	switch (col) {
	case fuCol_SHORT: return emKey_Short;
	case fuCol_UP: return (m_type == emTypeDown) ? emKey_Down : emKey_Up;
	case fuCol_UPBP: return (m_type == emTypeDown) ? emKey_DownBP : emKey_UpBP;
	default: return emKey_Unkown;
	}
}

void CreditDebtRankingUpdownList::setDoubleColor(double val, QColor& cr, QString& strText, bool needPercent, bool reverseColor/*=false*/)
{
	strText = "--";
	double dbCompare = 0.00499;
	//if (val < INVALID_PAN_DOUBLE){
	//	return;
	//}
	//QUOTEBOARD-12790 改为小于0.00499的数值置零
	if (val > -dbCompare && val < dbCompare) {
		if (needPercent) strText = "0.00%";
		else strText = "0";
		return;
	}
	QString strTemp = QString::asprintf("%.2f", val);
	strText = SSTools::PriceRemoveZero(strTemp, 0);
	if (val > dbCompare) {
		if (reverseColor) cr = StyleMgr::instance().color("Down_Reduce_H1");
		else cr = StyleMgr::instance().color("Up_Increase_H1");
		strText = "+" + strText;
	}
	else if (val < -dbCompare) {
		if (reverseColor) cr = StyleMgr::instance().color("Up_Increase_H1");
		else cr = StyleMgr::instance().color("Down_Reduce_H1");
	}
	if (needPercent) strText += "%";
}

//////////////////////////////////////////////////////////////////////////
CreditDebtRanking20DaysFirstList::CreditDebtRanking20DaysFirstList(QWidget* p, CreditDebtRankingData* data)
	: CreditDebtRankingList(p,data)
{
	m_sortinfo.InitData(getSortKey(fuCol_TIME), true);
	m_datainfo.type = CreditDebtRankingData::type_FirstDeal;
	m_datainfo.count = 20;
	m_datainfo.needcount = false;

	QVBoxLayout* main = dynamic_cast<QVBoxLayout*>(layout());
	if (main) {
		main->setContentsMargins(0, 0, 0, 0);
		main->setSpacing(5);
		SCheckComboBox* cb = new SCheckComboBox(this, true, NewStringTable::strFixedIncomeBondType(0));
		cb->setFixedHeight(24);
		connect(cb, &SCheckComboBox::selectionChanged, this, &CreditDebtRanking20DaysFirstList::onFilterChanged);
		main->insertWidget(0, cb);
	}
	initTable();
	updateTableHeader();
	updateBondPanCondition();
}

void CreditDebtRanking20DaysFirstList::initTable()
{
	m_tableSet = new STableColumnSet(m_table, "CreditDebtRanking20DaysFirstList", this);
	m_tableSet->setSaveCfg(true);
	BEGIN_COLUMN;
	ADD_COLUMN(fuCol_SHORT, m_tableSet, NewStringTable::strFixedIncome20DayFirstDeal(fuCol_SHORT), 0, 50, 50, 0.2, false, ALIGN_LEFT, kAuto, "");
	m_cols.push_back(fuCol_SHORT);
	ADD_COLUMN(fuCol_PRC, m_tableSet, NewStringTable::strFixedIncome20DayFirstDeal(fuCol_PRC), 0, 50, 50, 0.2, false, ALIGN_RIGHT, kAuto, "");
	m_cols.push_back(fuCol_PRC);
	ADD_COLUMN(fuCol_COUNT, m_tableSet, NewStringTable::strFixedIncome20DayFirstDeal(fuCol_COUNT), 0, 50, 50, 0.2, false, ALIGN_RIGHT, kAuto, "");
	m_cols.push_back(fuCol_COUNT);
	ADD_COLUMN(fuCol_LIQUIDITY, m_tableSet, NewStringTable::strFixedIncome20DayFirstDeal(fuCol_LIQUIDITY), 0, 50, 50, 0.2, true, ALIGN_RIGHT, kAuto, "");
	m_cols.push_back(fuCol_LIQUIDITY);
	ADD_COLUMN(fuCol_TIME, m_tableSet, NewStringTable::strFixedIncome20DayFirstDeal(fuCol_TIME), 0, 50, 50, 0.2, false, ALIGN_RIGHT, kAuto, "");
	m_cols.push_back(fuCol_TIME);

	m_tableSet->setMenuCfg(kDft);
	m_tableSet->apply();
	connect(m_table, &SVirtualTable::viewPosChanged, [=](int){updateTable(false);});
}

void CreditDebtRanking20DaysFirstList::updateTable(bool reset)
{
	QFont f = font();
	f.setPixelSize(13);
	f.setBold(true);

	unsigned int today = ServerTimeMgr::instance().today();
	QString strText;
	CBondContainer& bc = CBondContainer::instance();

	m_table->clearTable();

	int realCount = m_lstPDeal.size();
	int pageCount = m_table->pageCount();
	pageCount = std::min(pageCount, realCount);
	int pos = reset ? 0 : m_table->sliderPos();
	m_table->setRealDataCount(realCount);

	int colCount = m_model->columnCount();
	for (int row = 0; row < pageCount; ++row)
	{
		if (pos + row < 0 || pos + row >= (int)m_lstPDeal.size()) {
			break;
		}

		const CNewBondPanDeal& panDeal = m_lstPDeal[pos + row];
		int bondIndex = CBondContainer::instance().GetBondIndex(panDeal.m_bondkey, panDeal.m_listedmarket);
		if (!CBondContainer::instance().IsValidIndex(bondIndex)) return;
		const CBondInfo& bi = bc.ElementAtR(bondIndex);

		for (int col = 0; col < colCount; ++col)
		{
			if (!m_tableSet->isColVisible(col))
				continue;

			QStandardItem* item = m_model->item(row, col);
			if (item == nullptr) {
				item = new QStandardItem();
			}
			item->clearData();
			item->setData(StyleMgr::instance().color("Highlight"), Qt::ForegroundRole);
			item->setData((int)(Qt::AlignLeft|Qt::AlignVCenter), Qt::TextAlignmentRole);
			item->setData(StyleMgr::instance().color("BasicPlate"), Qt::BackgroundRole);
			item->setData(f, Qt::FontRole);
			QString idStr = QString::fromLocal8Bit(bi.GetBondCode());
			item->setData(idStr, DataIdRole);

			switch (col) {
			case fuCol_SHORT: {//债券简称			
				strText = QString::fromLocal8Bit(bi.GetBondShortName());
				item->setData(strText, Qt::DisplayRole);
				break;
			}
			case fuCol_PRC: { //价格
				strText = QString::asprintf("%s", panDeal.m_price);
				strText = SSTools::PriceRemoveZero(strText, 2);

				QString remark("");
				if (strcmp(bi.GetOptionType(), "NON") != 0 && strlen(bi.GetOptionType()) != 0) {
					if (panDeal.m_exercise[0] == '0'){
						remark = NewStringTable::strFixedIncomeQuoteRemark(0);//_T("行权");
					}
					else if (panDeal.m_exercise[0] == '1'){
						remark = NewStringTable::strFixedIncomeQuoteRemark(1);//_T("到期");
					}
				}

				if (strText != "--"){
					if (panDeal.IsCleanPrice()){
						//Item.strText3 = (m_bEnglishVersion ? NewStringTable.strNetPrice() : StringTable.strNetPrice());
					}
					else if (panDeal.IsFullPrice()){
						//Item.strText3 = (m_bEnglishVersion ? NewStringTable.strFullPrice() : StringTable.strFullPrice());
					}
				}

				if (!remark.isEmpty()) {
					item->setData(remark, Qt::ToolTipRole);
					SImage* img = ImgMgr::instance().image("widgets_grid_flag_triangle");
					QPixmap pixmap = QPixmap::fromImage(*img);
					item->setData(pixmap, Qt::DecorationRole);
				}

				item->setData((int)(Qt::AlignRight | Qt::AlignVCenter), Qt::TextAlignmentRole);
				item->setData(strText, Qt::DisplayRole);
				break;
			}
			case fuCol_COUNT: {//笔数
				strText = QString::asprintf("%d", panDeal.m_nCount);
				item->setData((int)(Qt::AlignRight | Qt::AlignVCenter), Qt::TextAlignmentRole);
				item->setData(strText, Qt::DisplayRole);
				break;
			}
			case fuCol_LIQUIDITY: {//流动性
				//if (bNormal) dbTemp = panDeal.m_closeGapBP;
				//else dbTemp = panDeal.m_cdcGapBP;
				//SetDoubleColor(dbTemp, Item.crFgClr, Item.strText, false, true);
				//if (m_type == emTypeDown) strText = QString::asprintf("%.4f", -panDeal.m_cdcGapBP);
				//else strText = QString::asprintf("%.4f", panDeal.m_cdcGapBP);
				item->setData((int)(Qt::AlignRight | Qt::AlignVCenter), Qt::TextAlignmentRole);
				item->setData(strText, Qt::DisplayRole);
				break;
			}
			case fuCol_TIME: {//时间
				time_t tmModify = panDeal.m_updateTime;
				strText = QString::asprintf("%lld", tmModify);
				setTransactionTime(CSSVContainer::GetServerTime(), tmModify, strText, true);
				item->setData((int)(Qt::AlignRight | Qt::AlignVCenter), Qt::TextAlignmentRole);
				item->setData(strText, Qt::DisplayRole);
				break;
			}
			default:
				break;
			}
			m_model->setItem(row, col, item);
		}
	}

	updateFlash();
}

sortKey CreditDebtRanking20DaysFirstList::getSortKey(int col)
{
	switch (col) {
	case fuCol_SHORT: return emKey_Short;
	case fuCol_PRC: return emKey_Price;
	case fuCol_COUNT: return emKey_Count;
	//case fuCol_LIQUIDITY: return emKey_Adv;
	case fuCol_TIME: return emKey_Time;
	default: return emKey_Unkown;
	}
}

void CreditDebtRanking20DaysFirstList::setTransactionTime(time_t tmCurrent, time_t tmModify, QString& strText, bool bUseDate)
{
	strText = "";

	if (tmCurrent <= 0 || tmModify <= 0) return;

	QDateTime ctmCurrent = QDateTime::fromTime_t(tmCurrent);
	QDateTime ctmModify = QDateTime::fromTime_t(tmModify);
	QDateTime ctmTempModify = ctmModify;

	ctmCurrent = QDateTime(ctmCurrent.date(), QTime(0, 0, 1));
	ctmModify = QDateTime(ctmModify.date(), QTime(0, 0, 1));

	int nDateTime = 24 * 60 * 60;
	if (ctmCurrent.date().month() == ctmModify.date().month() && ctmCurrent.date().day() == ctmModify.date().day()) {//同一天
		strText = QString::asprintf("%02d:%02d:%02d", ctmTempModify.time().hour(), ctmTempModify.time().minute(), ctmTempModify.time().second());
	}
	else if (bUseDate) {
		strText = QString::asprintf("%02d:%02d:%02d", ctmTempModify.time().hour(), ctmTempModify.time().minute(), ctmTempModify.time().second());
	}
	else if (ctmCurrent.time().addSecs(-ctmModify.time().second()).second() <= nDateTime) {//昨天
		strText = NewStringTable::strFixedIncomeYesterday();
	}
	else {
		int nCu = ctmCurrent.date().dayOfWeek();
		int nMo = ctmModify.date().dayOfWeek();
		ctmCurrent = ctmCurrent.addDays(-ctmModify.date().day());
		if (ctmCurrent.date().day() < nCu) {//同一周
			strText = NewStringTable::strFixedIncomeWeekDay(nMo - 1);
		} else {
			strText = QString::asprintf("%02d-%02d", ctmTempModify.date().month(), ctmTempModify.date().day());
		}
	}
}

void CreditDebtRanking20DaysFirstList::updateBondPanCondition() 
{
	std::vector<int> filter;
	if (m_data) {
		m_data->getFilter(filter);
	}

	SCheckComboBox* cb = getCheckComboBox();
	if (!cb) {
		return;
	}
	for (int i=0; i<(int)filter.size(); i++) {
		QString txt = NewStringTable::strFixedIncomeBondType(filter[i]);
		cb->addItem(txt);
	}
	cb->setCheck(0, true);
}

void CreditDebtRanking20DaysFirstList::onFilterChanged()
{
	if (!isVisible()) {
		return;
	}

	SCheckComboBox* cb = getCheckComboBox();
	if (!cb) {
		return;
	}
	std::vector<int> filter;
	for (int i=1; i<cb->count(); i++) {//从1开始，是去掉第一个checkbox全选
		if (cb->getCheck(i)) {
			filter.push_back(i);
		}
	}

	if (m_data) {
		m_data->setFilter(filter, 0);
	}
	onReloadData();
}

SCheckComboBox* CreditDebtRanking20DaysFirstList::getCheckComboBox() const
{
	QVBoxLayout* main = dynamic_cast<QVBoxLayout*>(this->layout());
	if (!main) {
		return nullptr;
	}
	QLayoutItem* item = main->itemAt(0);
	if (!item) {
		return nullptr;
	}
	return dynamic_cast<SCheckComboBox*>(item->widget());
}
